|
Feature |
Description |
Java 8+ Support |
Example |
Use Cases |
Advantages |
Disadvantages |
When to Use |
What to Do Instead with JDK < 8 (Classic Programming) |
Disadvantage of Classic Alternative |
1 |
Lambdas | Enables writing concise and expressive code with anonymous functions that can be passed as arguments. | Java 8+ | (a, b) -> a + b | Event handling, callback functions, collection transformations | Simplifies code, more readable | Debugging can be harder, less readable for complex logic | When writing concise, expressive code with no need for reuse | Use anonymous inner classes to implement interfaces, e.g., (new ActionListener() {...}) | Anonymous inner classes are more verbose, harder to debug, and lead to larger code size |
|
Feature |
Description |
Java 8+ Support |
Example |
Use Cases |
Advantages |
Disadvantages |
When to Use |
What to Do Instead with JDK < 8 (Classic Programming) |
Disadvantage of Classic Alternative |
2 |
Streams API | Allows functional-style operations on sequences of elements, e.g., filtering, mapping, reducing. | Java 8+ | stream.filter(x -> x > 5) | Data transformation, filtering collections, parallel processing | Efficient, concise, declarative style | Can be overused leading to performance bottlenecks | When processing collections or sequences of data | Use traditional for or foreach loops for iteration and manual filtering or mapping | More complex to manage iteration manually, prone to errors, and less readable |
|
Feature |
Description |
Java 8+ Support |
Example |
Use Cases |
Advantages |
Disadvantages |
When to Use |
What to Do Instead with JDK < 8 (Classic Programming) |
Disadvantage of Classic Alternative |
3 |
Immutability | Objects whose state cannot be changed after initialization, encouraging safe, side-effect-free code. | Java 8+ | List<String> list = List.of("A", "B"); | Multi-threaded applications, concurrency, safe state handling | Thread-safe, predictable behavior | More memory consumption (if creating many objects) | When dealing with shared or mutable state, or concurrency | Use final variables and avoid setters; ensure data is copied when needed | Manual deep copying can lead to inefficient memory usage and boilerplate code |
|
Feature |
Description |
Java 8+ Support |
Example |
Use Cases |
Advantages |
Disadvantages |
When to Use |
What to Do Instead with JDK < 8 (Classic Programming) |
Disadvantage of Classic Alternative |
4 |
First-Class Functions | Functions are first-class objects, meaning they can be passed as arguments, returned from other functions, and assigned to variables. | Java 8+ (via Lambdas) | Function<Integer, String> func = x -> String.valueOf(x); | Higher-order functions, callback handling | Flexibility, cleaner code | More abstract, could confuse developers unfamiliar with FP | When passing behavior (i.e., functions) as arguments | Use interfaces to pass behavior (e.g., Runnable, Callable) or anonymous classes | Interfaces can become overly complex or cluttered with many methods |
|
Feature |
Description |
Java 8+ Support |
Example |
Use Cases |
Advantages |
Disadvantages |
When to Use |
What to Do Instead with JDK < 8 (Classic Programming) |
Disadvantage of Classic Alternative |
5 |
Higher-Order Functions | Functions that take other functions as arguments or return functions as results. | Java 8+ (via Lambdas) | public static <T> Function<T, Integer> compose(Function<T, Integer> f) { return f.andThen(x -> x + 1); } | Function composition, custom transformations | Reduces code repetition, modularity | More abstract, harder to debug | When functions need to be reused or composed | Use nested functions or classes to simulate composition manually | Manual composition is error-prone, verbose, and can create unnecessary complexity |
|
Feature |
Description |
Java 8+ Support |
Example |
Use Cases |
Advantages |
Disadvantages |
When to Use |
What to Do Instead with JDK < 8 (Classic Programming) |
Disadvantage of Classic Alternative |
6 |
Map, Filter, Reduce | Common functional operations for processing collections (filtering, transforming, and reducing elements). | Java 8+ | stream.map(String::toUpperCase) | Data manipulation, collection processing, aggregations | Clear, declarative operations, easy chaining | Can lead to performance hits with large data | When performing transformations, filtering, or reductions on collections | Use loops, forEach, and manual if checks to filter, transform, or reduce data | Manual looping is more verbose, harder to manage, and prone to bugs |
|
Feature |
Description |
Java 8+ Support |
Example |
Use Cases |
Advantages |
Disadvantages |
When to Use |
What to Do Instead with JDK < 8 (Classic Programming) |
Disadvantage of Classic Alternative |
7 |
Optional | A container for optional values, preventing null references and forcing safe handling of absent values. | Java 8+ | Optional<String> opt = Optional.of("Hello"); | Avoiding NullPointerException, safe data retrieval | Avoids null references, clear intentions | Can introduce overhead if overused | When there is uncertainty about the presence of a value | Use null checks or try-catch blocks to handle nullability manually | Null checks can become cumbersome and less readable, leading to more complex code |
|
Feature |
Description |
Java 8+ Support |
Example |
Use Cases |
Advantages |
Disadvantages |
When to Use |
What to Do Instead with JDK < 8 (Classic Programming) |
Disadvantage of Classic Alternative |
8 |
Function Interfaces | Functional interfaces like Function, Predicate, Consumer, and Supplier represent various functions with different signatures. | Java 8+ | Predicate<Integer> isEven = x -> x % 2 == 0; | Reusable function definitions, higher-order functions | Modularity, reusability | More verbose, can add complexity | When creating reusable, composable functions | Define custom interfaces and implement them using anonymous classes or concrete classes | More boilerplate code, less concise |
|
Feature |
Description |
Java 8+ Support |
Example |
Use Cases |
Advantages |
Disadvantages |
When to Use |
What to Do Instead with JDK < 8 (Classic Programming) |
Disadvantage of Classic Alternative |
9 |
Pure Functions | Functions that do not have side effects and always return the same result for the same input. | Java 8+ (can be implemented) | public int add(int a, int b) { return a + b; } | Predictable, testable code, parallelism | No side effects, easy to test | Not suitable for I/O operations or state-modifying operations | When a function should be predictable, without side effects | Use static methods that don't modify external state or rely on class fields | Static methods for side-effect-free logic are more verbose and less flexible |
|
Feature |
Description |
Java 8+ Support |
Example |
Use Cases |
Advantages |
Disadvantages |
When to Use |
What to Do Instead with JDK < 8 (Classic Programming) |
Disadvantage of Classic Alternative |
10 |
Recursion | A function that calls itself, often used to replace iterative loops. | Java 8+ (can be implemented) | public int factorial(int n) { return (n == 1) ? 1 : n * factorial(n - 1); } | Problems involving tree structures, fractals | Simplifies complex algorithms, elegant solutions | Stack overflow issues, less performant | When recursion depth is large or performance is critical | Use traditional for or while loops instead of recursion for iterative solutions | Recursive solutions can be harder to read and prone to stack overflow if not optimized |
|
Feature |
Description |
Java 8+ Support |
Example |
Use Cases |
Advantages |
Disadvantages |
When to Use |
What to Do Instead with JDK < 8 (Classic Programming) |
Disadvantage of Classic Alternative |
11 |
Tail Recursion | Optimized recursion where the recursive call is the last operation, avoiding stack overflow. | Java does not natively optimize tail recursion, but it can be manually implemented | public int factorial(int n, int accumulator) { return (n == 1) ? accumulator : factorial(n - 1, n * accumulator); } | No stack overflow, more memory efficient | Needs manual optimization | When recursion depth is large or performance is critical | Use loops instead, as tail call optimization is not native to Java | Tail recursion is complex to implement and manage manually | |
|
Feature |
Description |
Java 8+ Support |
Example |
Use Cases |
Advantages |
Disadvantages |
When to Use |
What to Do Instead with JDK < 8 (Classic Programming) |
Disadvantage of Classic Alternative |
12 |
Memoization | Storing results of expensive function calls and reusing them when the same inputs occur. | Can be implemented manually. | Map<Integer, Integer> cache = new HashMap<>(); public int fibonacci(int n) { return cache.computeIfAbsent(n, x -> fibonacci(x - 1) + fibonacci(x - 2)); } | Improves performance for repeated function calls | Increased memory usage, more complex logic | When functions are repeatedly called with the same arguments | Use a Map or HashMap for manual caching in loops or function calls | Manual caching can increase memory usage and complicate code | |
|
Feature |
Description |
Java 8+ Support |
Example |
Use Cases |
Advantages |
Disadvantages |
When to Use |
What to Do Instead with JDK < 8 (Classic Programming) |
Disadvantage of Classic Alternative |
13 |
Type Inference | Java’s ability to infer the type of variables or expressions, reducing boilerplate code. | Java 10+ | var list = new ArrayList<String>(); | Reduces boilerplate, improves readability | May obscure the variable's type, reduces explicitness | When type clarity isn't critical or when using a concise syntax | Explicitly declare the type of variables and collections (e.g., ArrayList<String> list = new ArrayList<>();) | Explicit type declarations can clutter code, making it less flexible | |
|
Feature |
Description |
Java 8+ Support |
Example |
Use Cases |
Advantages |
Disadvantages |
When to Use |
What to Do Instead with JDK < 8 (Classic Programming) |
Disadvantage of Classic Alternative |
15 |
Method References | A shorthand notation for invoking a method on an object or class. | Java 8+ | List<String> list = Arrays.asList("a", "b"); list.forEach(System.out::println); | Cleaner, more concise code | Can become hard to debug with complex method references | When referring to existing methods to improve code readability | Use lambda expressions or explicitly call methods directly | Direct method calls can become verbose and less flexible | |
|
Feature |
Description |
Java 8+ Support |
Example |
Use Cases |
Advantages |
Disadvantages |
When to Use |
What to Do Instead with JDK < 8 (Classic Programming) |
Disadvantage of Classic Alternative |
17 |
Function Composition | Combining functions where the output of one function is passed as the input to another. | Java 8+ (via Function.andThen() or Function.compose()) | Function<Integer, Integer> addOne = x -> x + 1; Function<Integer, Integer> multiplyByTwo = x -> x * 2; Function<Integer, Integer> addOneThenMultiply = addOne.andThen(multiplyByTwo); | Reusable transformations, modular code | Can become less readable with many composed functions | When functions can be broken down into reusable, composable pieces | Manually chain method calls or use nested function calls | Chaining manually can lead to cluttered and hard-to-read code | |
|
Feature |
Description |
Java 8+ Support |
Example |
Use Cases |
Advantages |
Disadvantages |
When to Use |
What to Do Instead with JDK < 8 (Classic Programming) |
Disadvantage of Classic Alternative |
18 |
Lazy Evaluation | Delayed evaluation of expressions until their values are required, optimizing performance. | Java 8+ (via Stream API) | Stream<Integer> stream = Stream.of(1, 2, 3, 4); stream.filter(x -> x > 2).forEach(System.out::println); | Performance optimization, on-demand computation | Lazy streams can introduce complexity, harder to debug | When working with large datasets or computations that may not be needed | Use if conditions to control flow and computation | Manual flow control is less efficient and can complicate logic |
1. What is functional programming in Java?
Functional programming in Java is a programming paradigm that treats computation as the evaluation of mathematical functions and avoids changing state or mutable data. Java supports functional programming through features like lambda expressions, streams, and functional interfaces.
2. What are lambda expressions in Java?
Lambda expressions are a feature in Java introduced in Java 8, allowing you to express instances of functional interfaces (interfaces with a single abstract method) in a more concise and readable way. The syntax of a lambda expression is `(parameters) -> expression`.
List names = Arrays.asList("John", "Jane", "Doe");
names.forEach(name -> System.out.println(name));
3. What is a functional interface in Java?
A functional interface is an interface that contains exactly one abstract method, and it can have multiple default or static methods. These interfaces are used as the target types for lambda expressions and method references in Java.
4. How do you use the Stream API in Java?
The Stream API in Java allows you to process sequences of elements (like collections) in a functional style. You can use methods like `map()`, `filter()`, `reduce()`, `collect()`, etc., to process elements in a pipeline fashion.
List numbers = Arrays.asList(1, 2, 3, 4, 5);
int sum = numbers.stream()
.filter(n -> n % 2 == 0)
.mapToInt(Integer::intValue)
.sum();
System.out.println(sum); // Output: 6
5. What is the difference between `map()` and `flatMap()` in Java Streams?
The `map()` function transforms each element of the stream into another element, while `flatMap()` is used to flatten nested structures like lists within lists, transforming each element of the stream into a stream and then flattening them into a single stream.
6. What is the purpose of the `Optional` class in Java?
The `Optional` class is used to represent a value that may or may not be present. It is often used to avoid null pointer exceptions and provide a way to handle missing values more functionally, using methods like `ifPresent()`, `map()`, and `orElse()`.
Optional name = Optional.of("John");
name.ifPresent(n -> System.out.println("Hello, " + n));
7. How do you use method references in Java?
Method references in Java provide a shorthand way of writing lambda expressions that call a specific method. The syntax for method references is `ClassName::methodName`, and it can be used in place of lambda expressions where a method is directly invoked.
List names = Arrays.asList("John", "Jane", "Doe");
names.forEach(System.out::println); // Equivalent to: name -> System.out.println(name)
8. What is the `reduce()` function in Java Streams?
The `reduce()` function in Java Streams is used to combine elements of the stream into a single result, typically by performing some kind of aggregation or accumulation operation, such as sum, multiplication, etc.
List numbers = Arrays.asList(1, 2, 3, 4, 5);
int sum = numbers.stream().reduce(0, Integer::sum);
System.out.println(sum); // Output: 15
9. How do you filter elements in a stream in Java?
You can filter elements in a stream using the `filter()` method, which takes a predicate as an argument. It returns a new stream that only contains the elements that match the predicate.
List numbers = Arrays.asList(1, 2, 3, 4, 5);
List evenNumbers = numbers.stream()
.filter(n -> n % 2 == 0)
.collect(Collectors.toList());
System.out.println(evenNumbers); // Output: [2, 4]
10. What are the key benefits of functional programming in Java?
The key benefits of functional programming in Java include improved readability, less boilerplate code, easier parallelism, more declarative code, and better handling of side effects. It also promotes immutability and safer handling of state.
11. What is a higher-order function in Java?
A higher-order function is a function that takes one or more functions as parameters, returns a function as a result, or both. Java’s functional interfaces, lambda expressions, and method references allow for higher-order functions.
12. How does immutability work in functional programming in Java?
In functional programming, immutability refers to the idea that objects cannot be modified after they are created. In Java, this can be achieved by using final variables, making fields of objects final, and returning new objects rather than modifying existing ones.
13. What is the difference between `collect()` and `toList()` in Java Streams?
`collect()` is a terminal operation that transforms the elements of the stream into a different form, such as a collection. `toList()` is a collector that collects the stream elements into a `List`. While `toList()` is a specific collector, `collect()` is more general and can be used with any collector.
14. What does the `peek()` method do in Java Streams?
The `peek()` method in Java Streams is an intermediate operation that allows you to see the elements of the stream as they are processed. It is mainly used for debugging purposes or logging, as it does not modify the stream.
List numbers = Arrays.asList(1, 2, 3, 4, 5);
numbers.stream()
.peek(n -> System.out.println("Processing: " + n))
.map(n -> n * 2)
.collect(Collectors.toList());
15. What are default methods in Java interfaces?
Default methods are methods in interfaces that have a body. They allow interfaces to provide default implementations of methods, which helps maintain backward compatibility when new methods are added to interfaces.
16. How does Java handle side effects in functional programming?
In functional programming, side effects are discouraged. Java handles side effects by encouraging immutability, stateless functions, and the use of pure functions, which don’t change any state outside of their scope or rely on external state.
17. How can you create a stream from an array in Java?
You can create a stream from an array in Java using the `Arrays.stream()` method. This method returns a stream for the given array.
int[] numbers = {1, 2, 3, 4, 5};
IntStream stream = Arrays.stream(numbers);
stream.forEach(System.out::println);
18. What is a `UnaryOperator` in Java?
A `UnaryOperator` is a functional interface in Java that represents a function that takes one argument of a specific type and returns a result of the same type. It is a specialization of the `Function` interface for cases where the input and output types are the same.
UnaryOperator doubleValue = x -> x * 2;
System.out.println(doubleValue.apply(5)); // Output: 10
19. What is a `BiFunction` in Java?
A `BiFunction` is a functional interface in Java that represents a function that takes two arguments of possibly different types and returns a result of another type. It is often used to combine or transform two input values into one output value.
BiFunction add = (a, b) -> a + b;
System.out.println(add.apply(5, 10)); // Output: 15
20. How do you chain multiple operations in Java Streams?
In Java Streams, multiple operations can be chained together to form a pipeline. The intermediate operations (such as `map()`, `filter()`, etc.) are applied to the stream and the final result is produced by a terminal operation (like `collect()` or `forEach()`). Each operation returns a new stream.
List names = Arrays.asList("John", "Jane", "Alice", "Bob");
List result = names.stream()
.filter(name -> name.length() > 3)
.map(String::toUpperCase)
.collect(Collectors.toList());
System.out.println(result); // Output: [JOHN, JANE, ALICE]
21. What is a `Supplier` in Java?
A `Supplier` is a functional interface in Java that represents a function that takes no arguments and returns a result. It is often used when you need to supply a value but don't need to provide input data.
Supplier supplier = () -> "Hello, World!";
System.out.println(supplier.get()); // Output: Hello, World!
22. How can you use `Optional` to handle null values in Java?
`Optional` is a container object which may or may not contain a value. It is used to avoid `NullPointerException`. You can use methods like `isPresent()`, `ifPresent()`, or `orElse()` to handle values safely.
Optional name = Optional.ofNullable(null);
System.out.println(name.orElse("Default Value")); // Output: Default Value
23. What is the `reduce()` method in Java Streams?
The `reduce()` method in Java Streams is a terminal operation that combines the elements of a stream into a single result. It takes an associative binary operator and can be used to accumulate values, such as summing or multiplying numbers.
List numbers = Arrays.asList(1, 2, 3, 4, 5);
int sum = numbers.stream().reduce(0, (a, b) -> a + b);
System.out.println(sum); // Output: 15
24. What is a `Stream` in Java?
A `Stream` in Java is a sequence of elements supporting sequential and parallel aggregate operations. Streams are not data structures, but they provide a functional approach to processing data in a declarative manner.
25. How can you create an empty stream in Java?
You can create an empty stream in Java using the `Stream.empty()` method. This returns an empty stream with no elements.
Stream emptyStream = Stream.empty();
emptyStream.forEach(System.out::println); // No output
26. What is a `Consumer` in Java?
A `Consumer` is a functional interface that represents a function that takes one argument and returns no result. It is commonly used to perform operations like printing, modifying, or logging data.
Consumer printer = message -> System.out.println(message);
printer.accept("Hello, World!"); // Output: Hello, World!
27. What does the `map()` method do in Java Streams?
The `map()` method is an intermediate operation that transforms the elements of the stream by applying a function to each element. It produces a new stream consisting of the transformed elements.
List names = Arrays.asList("john", "jane", "bob");
List uppercasedNames = names.stream()
.map(String::toUpperCase)
.collect(Collectors.toList());
System.out.println(uppercasedNames); // Output: [JOHN, JANE, BOB]
28. What is the difference between `filter()` and `map()` in Java Streams?
`filter()` is used to remove elements from the stream based on a condition, whereas `map()` transforms the elements of the stream using a provided function. `filter()` returns a new stream with elements that match the condition, while `map()` changes each element of the stream.
29. How do you handle parallel streams in Java?
Parallel streams in Java are created by calling the `parallel()` method on a stream. This allows operations on the stream to be executed concurrently, which can improve performance on large datasets. However, you should use parallel streams with caution, as they may not always improve performance due to overhead or issues with thread safety.
List numbers = Arrays.asList(1, 2, 3, 4, 5);
numbers.parallelStream().forEach(System.out::println);
30. What is the significance of `forEach()` in Java Streams?
The `forEach()` method is a terminal operation that performs an action for each element of the stream. It is typically used for operations like printing or logging the elements of the stream. It cannot be used after a terminal operation as it consumes the stream.
List numbers = Arrays.asList(1, 2, 3, 4, 5);
numbers.stream().forEach(System.out::println);
31. What is the `flatMap()` method in Java Streams?
The `flatMap()` method is an intermediate operation that maps each element of the stream to another stream and flattens the resulting streams into a single stream. It is used when the transformation results in multiple elements per original element.
List> listOfLists = Arrays.asList(
Arrays.asList("apple", "banana"),
Arrays.asList("orange", "pear")
);
List flattenedList = listOfLists.stream()
.flatMap(List::stream)
.collect(Collectors.toList());
System.out.println(flattenedList); // Output: [apple, banana, orange, pear]
32. What is the difference between `collect()` and `toList()` in Java Streams?
`collect()` is a terminal operation that transforms a stream into a different form, typically a collection. `toList()` is a specific collector that collects the elements of the stream into a `List`. While `collect()` is a more general operation, `toList()` is a predefined collector for lists.
33. How can you find the maximum value in a stream in Java?
To find the maximum value in a stream, you can use the `max()` method with a comparator. This returns an `Optional` that contains the maximum value, or is empty if the stream is empty.
List numbers = Arrays.asList(1, 2, 3, 4, 5);
Optional max = numbers.stream().max(Integer::compareTo);
max.ifPresent(System.out::println); // Output: 5
34. What is method reference in Java and how is it used with streams?
A method reference in Java is a shorthand for lambda expressions that call a method. It is used to refer to a method of an object or class without executing it. In streams, method references can replace lambda expressions for invoking methods directly on elements of the stream.
List names = Arrays.asList("john", "jane", "bob");
names.stream().map(String::toUpperCase).forEach(System.out::println); // Output: JOHN, JANE, BOB
35. What does the `allMatch()` method do in Java Streams?
The `allMatch()` method is a short-circuiting terminal operation that checks if all elements in the stream satisfy a given predicate. It returns `true` if all elements match the predicate, or `false` otherwise.
List numbers = Arrays.asList(2, 4, 6, 8);
boolean allEven = numbers.stream().allMatch(n -> n % 2 == 0);
System.out.println(allEven); // Output: true
36. How do you handle exceptions in lambda expressions in Java?
Lambda expressions in Java do not allow checked exceptions directly. However, you can handle exceptions within a lambda by either catching them or using a custom wrapper method that handles the exception.
Runnable task = () -> {
try {
// Code that might throw an exception
} catch (Exception e) {
e.printStackTrace();
}
};
task.run();
37. What is the `forEachOrdered()` method in Java Streams?
The `forEachOrdered()` method is similar to `forEach()`, but it guarantees that the elements will be processed in the encounter order, even if the stream is processed in parallel. This is useful when the order of processing is important.
List names = Arrays.asList("john", "jane", "bob");
names.parallelStream().forEachOrdered(System.out::println);
38. How can you convert a stream into an array in Java?
To convert a stream into an array, you can use the `toArray()` method. This method returns an array containing the elements of the stream.
List numbers = Arrays.asList(1, 2, 3, 4, 5);
Integer[] array = numbers.stream().toArray(Integer[]::new);
System.out.println(Arrays.toString(array)); // Output: [1, 2, 3, 4, 5]
39. What is the purpose of the `peek()` method in Java Streams?
The `peek()` method is an intermediate operation that allows you to inspect the elements of the stream as they are processed. It is typically used for debugging or logging purposes. Note that it does not modify the elements of the stream.
List numbers = Arrays.asList(1, 2, 3, 4, 5);
numbers.stream().peek(System.out::println).map(n -> n * 2).collect(Collectors.toList());
40. What is `toMap()` in Java Streams?
The `toMap()` method is a collector in Java Streams that allows you to transform the elements of the stream into a map. You need to provide a key and a value for the map. The method returns a `Map` containing the elements of the stream.
List names = Arrays.asList("john", "jane", "bob");
Map nameMap = names.stream()
.collect(Collectors.toMap(String::length, name -> name));
System.out.println(nameMap); // Output: {4=john, 4=jane, 3=bob}
41. How does the `reduce()` method work in Java Streams?
The `reduce()` method is a terminal operation that combines the elements of the stream using an associative accumulation function. It produces a single result based on the stream elements.
List numbers = Arrays.asList(1, 2, 3, 4, 5);
int sum = numbers.stream().reduce(0, Integer::sum);
System.out.println(sum); // Output: 15
42. What is the purpose of the `Optional` class in Java Streams?
The `Optional` class is a container object which may or may not contain a value. It is used to avoid `NullPointerException` and to provide a way to handle missing values more gracefully. Many stream operations return `Optional` objects.
43. What is the `sorted()` method used for in Java Streams?
The `sorted()` method is an intermediate operation in Java Streams that returns a stream with the elements sorted according to their natural order or according to a provided comparator.
List numbers = Arrays.asList(5, 3, 8, 1);
List sortedNumbers = numbers.stream().sorted().collect(Collectors.toList());
System.out.println(sortedNumbers); // Output: [1, 3, 5, 8]
44. How do you handle multiple conditions using `filter()` in Java Streams?
You can combine multiple conditions in the `filter()` method using logical operators (`&&`, `||`, etc.) within a lambda expression.
List numbers = Arrays.asList(1, 2, 3, 4, 5, 6);
List filteredNumbers = numbers.stream()
.filter(n -> n % 2 == 0 && n > 2)
.collect(Collectors.toList());
System.out.println(filteredNumbers); // Output: [4, 6]
45. How do you use the `distinct()` method in Java Streams?
The `distinct()` method is an intermediate operation that eliminates duplicate elements from the stream.
List numbers = Arrays.asList(1, 2, 2, 3, 4, 4);
List distinctNumbers = numbers.stream().distinct().collect(Collectors.toList());
System.out.println(distinctNumbers); // Output: [1, 2, 3, 4]
46. What is the `anyMatch()` method used for in Java Streams?
The `anyMatch()` method is a short-circuiting terminal operation that checks if any element in the stream matches a given predicate. It returns `true` if at least one element matches, otherwise `false`.
List numbers = Arrays.asList(1, 2, 3, 4, 5);
boolean hasEven = numbers.stream().anyMatch(n -> n % 2 == 0);
System.out.println(hasEven); // Output: true
47. How can you check if a stream is empty in Java?
You can check if a stream is empty using the `findAny()` method combined with `isPresent()` to see if any element is present in the stream. If no element is found, the stream is empty.
List numbers = Arrays.asList();
boolean isEmpty = numbers.stream().findAny().isEmpty();
System.out.println(isEmpty); // Output: true
48. What is the difference between `count()` and `anyMatch()` in Java Streams?
The `count()` method returns the number of elements in the stream that match a given condition, while `anyMatch()` returns a boolean value indicating whether at least one element matches the condition.
49. How do you chain multiple operations in Java Streams?
You can chain multiple operations in Java Streams by calling stream methods consecutively. The stream is processed step by step in the order of method calls, and intermediate operations are lazily evaluated.
List numbers = Arrays.asList(1, 2, 3, 4, 5);
List result = numbers.stream()
.filter(n -> n % 2 == 0)
.map(n -> n * 2)
.collect(Collectors.toList());
System.out.println(result); // Output: [4, 8]
50. What is the purpose of the `skip()` method in Java Streams?
The `skip()` method is an intermediate operation that skips the first `n` elements of the stream and returns a new stream with the remaining elements.
List numbers = Arrays.asList(1, 2, 3, 4, 5);
List skippedNumbers = numbers.stream().skip(2).collect(Collectors.toList());
System.out.println(skippedNumbers); // Output: [3, 4, 5]
51. What is the `peek()` method in Java Streams used for?
The `peek()` method is an intermediate operation that allows you to inspect the elements of the stream as they are processed. It is often used for debugging purposes and does not alter the stream.
List numbers = Arrays.asList(1, 2, 3, 4, 5);
numbers.stream().peek(n -> System.out.println(n)).collect(Collectors.toList());
52. What is the `flatMap()` method in Java Streams?
The `flatMap()` method is an intermediate operation that allows you to transform each element into a stream and then flatten the resulting streams into a single stream.
List> numbers = Arrays.asList(Arrays.asList(1, 2), Arrays.asList(3, 4));
List flattened = numbers.stream().flatMap(List::stream).collect(Collectors.toList());
System.out.println(flattened); // Output: [1, 2, 3, 4]
53. How do you handle multiple streams concurrently in Java?
In Java, you can use the `parallel()` method to enable parallel processing of streams, which can improve performance for large datasets.
List numbers = Arrays.asList(1, 2, 3, 4, 5);
List squaredNumbers = numbers.parallelStream().map(n -> n * n).collect(Collectors.toList());
System.out.println(squaredNumbers);
54. What is the difference between `map()` and `flatMap()` in Java Streams?
The `map()` method transforms each element of the stream into a new element, while `flatMap()` transforms each element into a stream and then flattens the resulting streams into a single stream.
55. What is the `collect()` method in Java Streams?
The `collect()` method is a terminal operation that transforms the elements of a stream into a different form, such as a collection (e.g., List, Set, Map). It is typically used with `Collectors` utility methods.
List numbers = Arrays.asList(1, 2, 3, 4, 5);
List result = numbers.stream().collect(Collectors.toList());
System.out.println(result); // Output: [1, 2, 3, 4, 5]
56. How do you use the `groupingBy()` collector in Java Streams?
The `groupingBy()` collector is a convenient way to group elements of a stream based on a classifier function. It returns a Map where the key is the result of applying the classifier function to each element.
List numbers = Arrays.asList(1, 2, 3, 4, 5, 6, 7);
Map> grouped = numbers.stream()
.collect(Collectors.groupingBy(n -> n % 2));
System.out.println(grouped); // Output: {0=[2, 4, 6], 1=[1, 3, 5, 7]}
57. What is the `toMap()` collector used for in Java Streams?
The `toMap()` collector is used to accumulate elements of the stream into a Map. It requires two functions: one to extract the key and one to extract the value for each element.
List names = Arrays.asList("Alice", "Bob", "Charlie");
Map map = names.stream()
.collect(Collectors.toMap(String::length, Function.identity()));
System.out.println(map); // Output: {5=Alice, 3=Bob, 7=Charlie}
58. How do you handle null values in Java Streams?
You can handle null values in Java Streams by using `filter()` to exclude them, or by using `Optional` to wrap potentially null values and avoid `NullPointerException`.
List names = Arrays.asList("Alice", null, "Bob", "Charlie");
List nonNullNames = names.stream().filter(Objects::nonNull).collect(Collectors.toList());
System.out.println(nonNullNames); // Output: [Alice, Bob, Charlie]
59. What does the `findFirst()` method do in Java Streams?
The `findFirst()` method is a terminal operation that returns the first element in the stream that matches the specified condition, if any. It returns an `Optional`.
List numbers = Arrays.asList(1, 2, 3, 4, 5);
Optional firstEven = numbers.stream().filter(n -> n % 2 == 0).findFirst();
firstEven.ifPresent(System.out::println); // Output: 2
60. How do you perform an operation on each element in a stream without modifying the stream?
You can use the `forEach()` method to perform an action on each element in the stream. This is a terminal operation that doesn't alter the stream itself.
List numbers = Arrays.asList(1, 2, 3, 4, 5);
numbers.stream().forEach(n -> System.out.println(n));
61. What is the `reduce()` method in Java Streams?
The `reduce()` method is a terminal operation that performs a reduction on the elements of the stream using an associative accumulation function. It produces a single result.
List numbers = Arrays.asList(1, 2, 3, 4, 5);
int sum = numbers.stream().reduce(0, (a, b) -> a + b);
System.out.println(sum); // Output: 15
62. What is a `Supplier` in Java Functional Interfaces?
A `Supplier` is a functional interface that represents a supplier of results. It does not take any arguments but returns a result.
Supplier randomSupplier = () -> (int)(Math.random() * 100);
System.out.println(randomSupplier.get()); // Output: Random number
63. What is a `Consumer` in Java Functional Interfaces?
A `Consumer` is a functional interface that represents an operation that takes a single input argument and returns no result. It is used to perform an action on an input.
Consumer printConsumer = str -> System.out.println(str);
printConsumer.accept("Hello, World!"); // Output: Hello, World!
64. How does the `mapToInt()` method work in Java Streams?
The `mapToInt()` method is an intermediate operation that converts a stream of objects to an `IntStream`. It applies a function to each element and returns an integer value.
List numbers = Arrays.asList("1", "2", "3", "4");
int sum = numbers.stream().mapToInt(Integer::parseInt).sum();
System.out.println(sum); // Output: 10
65. What is the `anyMatch()` method in Java Streams?
The `anyMatch()` method is a terminal operation that checks whether any elements in the stream satisfy the given predicate. It returns `true` if any element matches the condition, otherwise `false`.
List numbers = Arrays.asList(1, 2, 3, 4, 5);
boolean hasEven = numbers.stream().anyMatch(n -> n % 2 == 0);
System.out.println(hasEven); // Output: true
66. What is the `allMatch()` method in Java Streams?
The `allMatch()` method is a terminal operation that checks whether all elements in the stream satisfy the given predicate. It returns `true` if all elements match the condition, otherwise `false`.
List numbers = Arrays.asList(2, 4, 6, 8);
boolean allEven = numbers.stream().allMatch(n -> n % 2 == 0);
System.out.println(allEven); // Output: true
67. How does the `noneMatch()` method work in Java Streams?
The `noneMatch()` method is a terminal operation that checks whether no elements in the stream satisfy the given predicate. It returns `true` if no elements match the condition, otherwise `false`.
List numbers = Arrays.asList(1, 2, 3, 4, 5);
boolean noEven = numbers.stream().noneMatch(n -> n % 2 != 0);
System.out.println(noEven); // Output: false
68. What is the `forEachOrdered()` method in Java Streams?
The `forEachOrdered()` method is a terminal operation that performs an action for each element in the stream in the encounter order. It is used when you want to preserve the order of elements while processing them in parallel streams.
List names = Arrays.asList("Alice", "Bob", "Charlie");
names.parallelStream().forEachOrdered(System.out::println);
69. What is the `skip()` method used for in Java Streams?
The `skip()` method is an intermediate operation that skips the first `n` elements of the stream and returns a new stream with the remaining elements.
List numbers = Arrays.asList(1, 2, 3, 4, 5);
List skipped = numbers.stream().skip(2).collect(Collectors.toList());
System.out.println(skipped); // Output: [3, 4, 5]
70. How do you use the `limit()` method in Java Streams?
The `limit()` method is an intermediate operation that returns a new stream containing the first `n` elements from the original stream. It is useful for restricting the number of elements in a stream.
List numbers = Arrays.asList(1, 2, 3, 4, 5);
List limited = numbers.stream().limit(3).collect(Collectors.toList());
System.out.println(limited); // Output: [1, 2, 3]
71. What is the `flatMap()` method in Java Streams?
The `flatMap()` method is an intermediate operation that transforms each element of the stream into a new stream and then flattens the result into a single stream.
List> listOfLists = Arrays.asList(
Arrays.asList("a", "b", "c"),
Arrays.asList("d", "e")
);
List flattened = listOfLists.stream().flatMap(List::stream).collect(Collectors.toList());
System.out.println(flattened); // Output: [a, b, c, d, e]
72. What is a `Predicate` in Java Functional Interfaces?
A `Predicate` is a functional interface that represents a boolean-valued function of one argument. It is typically used to test whether a condition is true or false for an object.
Predicate isEven = n -> n % 2 == 0;
System.out.println(isEven.test(4)); // Output: true
73. How does the `distinct()` method work in Java Streams?
The `distinct()` method is an intermediate operation that removes duplicate elements from a stream based on the `equals()` method.
List numbers = Arrays.asList(1, 2, 2, 3, 4, 4, 5);
List distinctNumbers = numbers.stream().distinct().collect(Collectors.toList());
System.out.println(distinctNumbers); // Output: [1, 2, 3, 4, 5]
74. What is the `toArray()` method used for in Java Streams?
The `toArray()` method is a terminal operation that converts a stream into an array. You can pass a function that returns an array of the correct type.
List words = Arrays.asList("apple", "banana", "cherry");
String[] array = words.stream().toArray(String[]::new);
System.out.println(Arrays.toString(array)); // Output: [apple, banana, cherry]
75. What is a `Function` in Java Functional Interfaces?
A `Function` is a functional interface that represents a function that takes one argument and produces a result. It is typically used for mapping one type to another.
Function stringLength = str -> str.length();
System.out.println(stringLength.apply("Hello")); // Output: 5
76. How does the `sorted()` method work in Java Streams?
The `sorted()` method is an intermediate operation that sorts the elements of a stream in natural order or using a comparator.
List numbers = Arrays.asList(5, 1, 3, 4, 2);
List sortedNumbers = numbers.stream().sorted().collect(Collectors.toList());
System.out.println(sortedNumbers); // Output: [1, 2, 3, 4, 5]
77. What is the `peek()` method used for in Java Streams?
The `peek()` method is an intermediate operation that allows you to perform a side-effect operation on each element of the stream without consuming it. It is often used for debugging.
List numbers = Arrays.asList(1, 2, 3, 4, 5);
numbers.stream().peek(n -> System.out.println("Processing: " + n)).forEach(System.out::println);
78. What is the difference between `map()` and `flatMap()` in Java Streams?
The `map()` method transforms each element of the stream into a new value, while `flatMap()` transforms each element into a stream and then flattens the resulting streams into a single stream.
79. How do you use the `forEach()` method in Java Streams?
The `forEach()` method is a terminal operation that iterates over each element of the stream and performs a specified action.
List names = Arrays.asList("Alice", "Bob", "Charlie");
names.stream().forEach(System.out::println);
80. What is a `UnaryOperator` in Java Functional Interfaces?
A `UnaryOperator` is a functional interface that represents an operation on a single operand that produces a result of the same type as the operand.
UnaryOperator square = x -> x * x;
System.out.println(square.apply(5)); // Output: 25
81. What is the `collect()` method in Java Streams?
The `collect()` method is a terminal operation that transforms the elements of a stream into a different form, usually a collection like a List, Set, or Map.
List numbers = Arrays.asList(1, 2, 3, 4);
List doubled = numbers.stream().map(n -> n * 2).collect(Collectors.toList());
System.out.println(doubled); // Output: [2, 4, 6, 8]
82. What is the difference between `findFirst()` and `findAny()` in Java Streams?
The `findFirst()` method returns the first element in the stream, while `findAny()` can return any element from the stream. `findAny()` is typically used in parallel streams.
83. What is `Optional` in Java and how is it used in functional programming?
`Optional` is a container object that may or may not contain a non-null value. It is used to represent a value that may be absent, allowing safe handling of null values.
Optional name = Optional.ofNullable("John");
System.out.println(name.orElse("Default")); // Output: John
84. What is the `anyMatch()` method in Java Streams?
The `anyMatch()` method is a terminal operation that checks whether at least one element of the stream matches the given predicate.
List numbers = Arrays.asList(1, 2, 3, 4);
boolean hasEven = numbers.stream().anyMatch(n -> n % 2 == 0);
System.out.println(hasEven); // Output: true
85. How do you use the `reduce()` method in Java Streams?
The `reduce()` method is a terminal operation that performs a reduction on the elements of the stream using an associative accumulation function and returns an `Optional` containing the result.
List numbers = Arrays.asList(1, 2, 3, 4);
int sum = numbers.stream().reduce(0, (a, b) -> a + b);
System.out.println(sum); // Output: 10
86. What is the `IntStream` in Java Streams?
`IntStream` is a specialized stream for working with primitive `int` values. It provides methods that are optimized for working with primitive values, reducing the overhead of autoboxing.
IntStream.range(1, 5).forEach(System.out::println); // Output: 1, 2, 3, 4
87. How does the `skip()` method work in Java Streams?
The `skip()` method is an intermediate operation that skips the first `n` elements of the stream and returns a stream with the remaining elements.
List numbers = Arrays.asList(1, 2, 3, 4, 5);
List skipped = numbers.stream().skip(2).collect(Collectors.toList());
System.out.println(skipped); // Output: [3, 4, 5]
88. What is the `limit()` method in Java Streams?
The `limit()` method is an intermediate operation that returns a stream with at most the specified number of elements, truncating the stream if it is larger.
List numbers = Arrays.asList(1, 2, 3, 4, 5);
List limited = numbers.stream().limit(3).collect(Collectors.toList());
System.out.println(limited); // Output: [1, 2, 3]
89. How do you use the `mapToInt()` method in Java Streams?
The `mapToInt()` method is used to convert a stream of objects to a stream of primitive `int` values. It is commonly used when you need to perform numeric operations on the stream elements.
List numbers = Arrays.asList("1", "2", "3", "4");
int sum = numbers.stream().mapToInt(Integer::parseInt).sum();
System.out.println(sum); // Output: 10
90. What is a `BiFunction` in Java Functional Interfaces?
A `BiFunction` is a functional interface that takes two arguments of different types and produces a result. It is commonly used for functions that take two inputs and return a result.
BiFunction add = (a, b) -> a + b;
System.out.println(add.apply(2, 3)); // Output: 5
91. What is the difference between `map()` and `flatMap()` in Java Streams?
The `map()` method transforms each element of the stream into a new form, while `flatMap()` flattens the result into a single stream when the mapping produces multiple elements per input.
List words = Arrays.asList("Hello", "World");
List characters = words.stream()
.flatMap(word -> Arrays.stream(word.split("")))
.collect(Collectors.toList());
System.out.println(characters); // Output: [H, e, l, l, o, W, o, r, l, d]
92. What is the `UnaryOperator` functional interface in Java?
A `UnaryOperator` is a functional interface that takes one argument and returns a result of the same type. It is used for functions that perform operations on a single input and return the same type.
UnaryOperator square = x -> x * x;
System.out.println(square.apply(5)); // Output: 25
93. How do you use `Stream.of()` in Java?
`Stream.of()` is a static method that creates a stream from a specified set of elements.
Stream stream = Stream.of("Java", "Python", "C++");
stream.forEach(System.out::println); // Output: Java, Python, C++
94. What is the `Function` interface in Java?
`Function` is a functional interface that takes one argument and returns a result. It is commonly used for mapping functions or operations that transform data.
Function numberToString = n -> "Number: " + n;
System.out.println(numberToString.apply(5)); // Output: Number: 5
95. How does the `forEach()` method work in Java Streams?
The `forEach()` method is a terminal operation that performs an action for each element in the stream. It is often used to iterate over elements in a stream.
List numbers = Arrays.asList(1, 2, 3);
numbers.stream().forEach(System.out::println); // Output: 1, 2, 3
96. What is the `Comparator` interface in Java?
`Comparator` is a functional interface used for comparing two objects. It is often used for sorting elements in a stream or a collection.
List numbers = Arrays.asList(5, 3, 8, 1);
numbers.stream().sorted(Comparator.naturalOrder()).forEach(System.out::println); // Output: 1, 3, 5, 8
97. What is `reduce()` used for in Java Streams?
`reduce()` is a terminal operation used to combine all elements in a stream into a single result. It uses an associative accumulation function.
List numbers = Arrays.asList(1, 2, 3, 4);
int sum = numbers.stream().reduce(0, (a, b) -> a + b);
System.out.println(sum); // Output: 10
98. What is the `IntStream` in Java?
`IntStream` is a specialized stream for working with primitive `int` values. It provides methods that reduce overhead and improve performance when working with primitive data types.
IntStream.range(1, 5).forEach(System.out::println); // Output: 1, 2, 3, 4
99. How can you create a Stream from an array in Java?
You can use `Arrays.stream()` to create a stream from an array.
int[] arr = {1, 2, 3, 4};
IntStream stream = Arrays.stream(arr);
stream.forEach(System.out::println); // Output: 1, 2, 3, 4
100. How do you use `Stream.generate()` in Java?
`Stream.generate()` is a method that generates an infinite stream based on a provided `Supplier`. You can limit the size of the stream using `limit()` to prevent it from running indefinitely.
Stream randomNumbers = Stream.generate(() -> (int) (Math.random() * 100));
randomNumbers.limit(5).forEach(System.out::println); // Output: random numbers between 0 and 100
101. What is the `Supplier` functional interface in Java?
The `Supplier` functional interface represents a supplier of results. It has a method `get()` that doesn't take any input parameters and returns a value.
Supplier stringSupplier = () -> "Hello, World!";
System.out.println(stringSupplier.get()); // Output: Hello, World!
102. How does `Stream.filter()` work in Java?
`Stream.filter()` is a method that returns a new stream containing only elements that match the specified predicate. It is often used to filter out unwanted elements.
List numbers = Arrays.asList(1, 2, 3, 4, 5);
numbers.stream().filter(n -> n % 2 == 0).forEach(System.out::println); // Output: 2, 4
103. What is the `Optional` class in Java?
`Optional` is a container object which may or may not contain a value. It is used to represent the possibility of a null value and helps avoid `NullPointerException`.
Optional optional = Optional.of("Hello");
optional.ifPresent(System.out::println); // Output: Hello
104. How can you create an immutable collection in Java?
Java provides the `Collections.unmodifiableList()`, `unmodifiableSet()`, and `unmodifiableMap()` methods to create immutable collections. In addition, you can use `List.of()` and `Set.of()` in Java 9 and later.
List immutableList = List.of("A", "B", "C");
System.out.println(immutableList); // Output: [A, B, C]
105. What is the use of `Stream.peek()` in Java?
`Stream.peek()` is an intermediate operation that allows you to perform a side effect on each element of the stream as it is processed. It is primarily used for debugging purposes.
List numbers = Arrays.asList(1, 2, 3, 4);
numbers.stream()
.peek(n -> System.out.println("Processing: " + n))
.collect(Collectors.toList());
106. How does `Stream.concat()` work in Java?
`Stream.concat()` is a method that merges two streams into a single stream. It takes two streams as parameters and returns a new stream that contains the elements of both.
Stream stream1 = Stream.of("A", "B");
Stream stream2 = Stream.of("C", "D");
Stream combined = Stream.concat(stream1, stream2);
combined.forEach(System.out::println); // Output: A, B, C, D
107. How do you use `Stream.collect()` in Java?
`Stream.collect()` is a terminal operation that transforms the elements of the stream into a different form, typically a collection, such as a list, set, or map.
List numbers = Arrays.asList(1, 2, 3, 4);
List evenNumbers = numbers.stream()
.filter(n -> n % 2 == 0)
.collect(Collectors.toList());
System.out.println(evenNumbers); // Output: [2, 4]
108. What is `Stream.allMatch()` in Java?
`Stream.allMatch()` is a terminal operation that checks if all elements in the stream satisfy the given predicate.
List numbers = Arrays.asList(2, 4, 6, 8);
boolean allEven = numbers.stream().allMatch(n -> n % 2 == 0);
System.out.println(allEven); // Output: true
109. What is the difference between `limit()` and `skip()` in Java Streams?
`limit()` is an operation that truncates the stream to a specified size, while `skip()` is used to skip a specified number of elements from the beginning of the stream.
List numbers = Arrays.asList(1, 2, 3, 4, 5);
numbers.stream().limit(3).forEach(System.out::println); // Output: 1, 2, 3
numbers.stream().skip(2).forEach(System.out::println); // Output: 3, 4, 5
110. How does `Stream.forEachOrdered()` work in Java?
`Stream.forEachOrdered()` is similar to `forEach()`, but it guarantees the elements are processed in the encounter order if the stream has an encounter order.
Stream.of(1, 2, 3, 4)
.parallel()
.forEachOrdered(System.out::println); // Output: 1, 2, 3, 4 (order preserved)
111. What is the `Consumer` functional interface in Java?
`Consumer` is a functional interface that represents an operation that accepts a single input argument and returns no result. It has the method `accept()`.
Consumer printConsumer = s -> System.out.println(s);
printConsumer.accept("Hello"); // Output: Hello
112. How do you use `Stream.reduce()` in Java?
`Stream.reduce()` is a terminal operation that performs a reduction on the elements of the stream using an associative accumulation function and returns an `Optional` result.
List numbers = Arrays.asList(1, 2, 3, 4);
int sum = numbers.stream().reduce(0, Integer::sum);
System.out.println(sum); // Output: 10
113. What is `Stream.flatMap()` used for in Java?
`Stream.flatMap()` is an intermediate operation that replaces each element of the stream with a stream of new values, then flattens the resulting streams into a single stream.
List> listOfLists = Arrays.asList(
Arrays.asList(1, 2),
Arrays.asList(3, 4)
);
List flatList = listOfLists.stream()
.flatMap(List::stream)
.collect(Collectors.toList());
System.out.println(flatList); // Output: [1, 2, 3, 4]
114. What is the difference between `map()` and `flatMap()` in Java Streams?
`map()` transforms each element into one element, while `flatMap()` can transform each element into zero, one, or more elements and flattens the result into a single stream.
Stream words = Stream.of("hello", "world");
Stream uppercased = words.map(String::toUpperCase); // [HELLO, WORLD]
Stream flatMapExample = Stream.of(Arrays.asList("a", "b"), Arrays.asList("c", "d"))
.flatMap(List::stream); // [a, b, c, d]
115. How does `Stream.distinct()` work in Java?
`Stream.distinct()` is an intermediate operation that returns a stream with distinct elements (removes duplicates) according to the `equals()` method.
List numbers = Arrays.asList(1, 2, 2, 3, 3, 4);
numbers.stream().distinct().forEach(System.out::println); // Output: 1, 2, 3, 4
116. What is `Stream.anyMatch()` in Java?
`Stream.anyMatch()` is a terminal operation that checks whether any element in the stream matches the provided predicate. It returns `true` if at least one element satisfies the condition.
List numbers = Arrays.asList(1, 2, 3, 4);
boolean hasEven = numbers.stream().anyMatch(n -> n % 2 == 0);
System.out.println(hasEven); // Output: true
117. How does `Stream.noneMatch()` work in Java?
`Stream.noneMatch()` is a terminal operation that checks if no elements in the stream match the given predicate. It returns `true` if none of the elements satisfy the condition.
List numbers = Arrays.asList(1, 3, 5);
boolean noEven = numbers.stream().noneMatch(n -> n % 2 == 0);
System.out.println(noEven); // Output: true
118. What is the purpose of `Stream.sorted()` in Java?
`Stream.sorted()` is an intermediate operation that returns a stream with elements sorted according to the natural order or using a custom comparator.
List numbers = Arrays.asList(5, 3, 2, 4, 1);
numbers.stream().sorted().forEach(System.out::println); // Output: 1, 2, 3, 4, 5
119. What is the `Function` functional interface in Java?
`Function` is a functional interface that represents a function that accepts one argument and produces a result. It has the method `apply()`.
Function lengthFunction = String::length;
System.out.println(lengthFunction.apply("Hello")); // Output: 5
120. How do you use `Stream.toList()` in Java?
`Stream.toList()` is a terminal operation that collects the elements of a stream into a new list. This method was introduced in Java 16.
List numbers = Stream.of(1, 2, 3, 4).toList();
System.out.println(numbers); // Output: [1, 2, 3, 4]